﻿using System;
using System.IO;
using System.Text;
using System.Xml;
using System.Xml.Serialization;

namespace Tzw.Common
{
    /// <summary>
    /// XML序列化公共处理类
    /// </summary>
    public static class XmlHelper
    {
        #region xml序列化和反序列化


        /// <summary>
        /// 将实体对象转换成XML
        /// </summary>
        /// <typeparam name="T">实体类型</typeparam>
        /// <param name="obj">实体对象</param>
        //public static string XmlSerialize<T>(T obj)
        //{
        //    try
        //    {
        //        using (StringWriter sw = new StringWriter())
        //        {
        //            var serializer = new XmlSerializer(obj.GetType());
        //            serializer.Serialize(sw, obj);
        //            sw.Close();
        //            return sw.ToString();
        //        }
        //    }
        //    catch (Exception ex)
        //    {
        //        throw new Exception("将实体对象转换成XML异常", ex);
        //    }
        //}

        /// <summary>
        /// 序列化
        /// </summary>
        /// <param name="obj">对象</param>
        /// <returns></returns>
        public static string Serializer(object obj)
        {
            var settings = new XmlWriterSettings
            {
                Indent = true,
                IndentChars = " ",
                NewLineChars = "\r\n",
                Encoding = Encoding.UTF8,
                OmitXmlDeclaration = true // 不生成声明头
            };

            var stream = new MemoryStream();
            var xml = new XmlSerializer(obj.GetType());

            using (var xmlWriter = XmlWriter.Create(stream, settings))
            {
                var xns = new XmlSerializerNamespaces();
                xns.Add(string.Empty, string.Empty);
                //序列化对象
                xml.Serialize(xmlWriter, obj, xns);
                xmlWriter.Close();
            }

            stream.Position = 0;
            var sr = new StreamReader(stream);
            var str = sr.ReadToEnd();

            sr.Dispose();
            stream.Dispose();

            return str;
        }

        /// <summary>
        /// 将XML转换成实体对象
        /// </summary>
        /// <typeparam name="T">实体类型</typeparam>
        /// <param name="strXML">XML</param>
        public static T DeSerializer<T>(string strXML) where T : class
        {
            try
            {
                using (var sr = new StringReader(strXML))
                {
                    var serializer = new XmlSerializer(typeof(T));
                    return serializer.Deserialize(sr) as T;
                }
            }
            catch (Exception ex)
            {
                throw new Exception("将XML转换成实体对象异常", ex);
            }
        }

        #endregion

        #region xml CDATA节点读取

        /// <summary>
        /// 获取CDDATA内容
        /// </summary>
        /// <param name="doc"></param>
        /// <param name="xmlStr">xml内容</param>
        /// <param name="nodePath">节点路径</param>
        /// <returns></returns>
        public static string GetCdData(this XmlDocument doc, string xmlStr, string nodePath)
        {
            doc.LoadXml(xmlStr);
            return doc.SelectSingleNode(nodePath)?.InnerText;
        }

        /// <summary>
        /// 获取CDDATA内容，已加载节点内容后使用该方法
        /// </summary>
        /// <param name="doc"></param>
        /// <param name="nodePath">节点路径</param>
        /// <returns></returns>
        public static string GetCdData(this XmlDocument doc, string nodePath)
        {
            return doc.SelectSingleNode(nodePath)?.InnerText;
        }

        #endregion
    }
}
